<template>
  <div class="wrapper" ref="container_warp">
    <div class="title">业务流程图（自动布局）</div>
    <div class="search">
      <el-select v-model="selectedType" @change="onTypeChange" style="width: 240px">
        <el-option v-for="item in typeList" :key="item.value" :label="item.label" :value="item.value" />
      </el-select>
      <el-select v-model="selectedSubType" @change="fetchAndRender" style="width: 240px; margin-left: 10px">
        <el-option v-for="item in subTypeList" :key="item.value" :label="item.label" :value="item.value" />
      </el-select>
      <span style="display: inline-block; margin-left: 16px; font-size: 14px">预期可开工时间：2025-09-03</span>
    </div>
    <div id="container"></div>

    <NodeDialog v-if="nodeDialogVisible" v-model:dialogVisible="nodeDialogVisible" />
  </div>
</template>

<script setup>
import { ref, onMounted, nextTick, onUnmounted } from 'vue'
import { Graph } from '@antv/x6'
import { autoLayout } from './common'
// import axios from 'axios'
import '@antv/x6-vue-shape'
import FlowNode from './flowNode.vue'
import { mockFlowData, mockSubTypeList } from './mock.js'
import NodeDialog from './nodeDialog.vue'

const selectedType = ref('1')
const selectedSubType = ref('1')
const typeList = ref([
  { value: '1', label: '钢轨大中修项目' },
  { value: '2', label: '投资项目' },
])
const subTypeList = ref(mockSubTypeList[1]) // 二级下拉框
const graph = ref(null)
const container_warp = ref(null)

const onTypeChange = () => {
  // 假设 mockSubTypeList[selectedType.value] 是二级下拉数据
  subTypeList.value = mockSubTypeList[selectedType.value] || []
  selectedSubType.value = ''
}

// 注册自定义节点和边
const registCustom = () => {
  Graph.registerEdge(
    'bpmn-edge',
    {
      inherit: 'edge',
      attrs: { line: { stroke: '#81d2f7', strokeWidth: 4 } },
    },
    true,
  )
  Graph.registerNode(
    'my-node',
    {
      inherit: 'vue-shape',
      width: 200,
      height: 180,
      component: { template: `<FlowNode />`, components: { FlowNode } },
    },
    true,
  )
}
// 获取数据并渲染
const fetchAndRender = async () => {
  if (!graph.value || typeof graph.value.fromJSON !== 'function') {
    // 还没初始化好，直接返回
    return
  }
  if (!selectedType.value || !selectedSubType.value) return

  try {
    // 本地开发用 mock 数据
    const mockData = mockFlowData
    // 实际联调用 axios
    // const res = await axios.get(`/api/flow?projectType=${selectedType.value}`)
    // const mockData = res.data

    const { nodes, edges } = mockData
    const layoutedNodes = autoLayout(nodes, edges)

    const x6Data = {
      nodes: layoutedNodes.map((n) => ({
        ...n,
        shape: 'my-node',
        data: n.data || {},
      })),
      edges: edges.map((e) => ({
        ...e,
        shape: 'bpmn-edge',
        router: { name: 'manhattan' },
      })),
    }
    graph.value.fromJSON(x6Data)
  } catch (error) {
    console.error('获取数据失败:', error)
  }
}
const resizeGraph = () => {
  if (graph.value) {
    const rect = container_warp.value.getBoundingClientRect()
    graph.value.resize(rect.width, rect.height)
  }
}
// 弹窗
const nodeDialogVisible = ref(false)
const initX6Node = () => {
  const rect = container_warp.value.getBoundingClientRect()
  graph.value = new Graph({
    container: document.getElementById('container'),
    width: rect.width,
    height: rect.height,
    connecting: { router: 'orth' },
    interacting: false,
    scroller: { enabled: false, pannable: true, padding: 0, pageVisible: false, autoResize: true },
    mousewheel: { enabled: true, zoomAtMousePosition: true, modifiers: 'ctrl', minScale: 0.2, maxScale: 2 },
    panning: { enabled: true, eventTypes: ['leftMouseDown', 'rightMouseDown', 'middleMouseDown'] },
  })
  fetchAndRender()
  resizeGraph()
  // 监听自定义事件
  graph.value.on('openDialog', (data) => {
    if (data.tasks > 0) {
      nodeDialogVisible.value = true
    }
  })
}

onMounted(() => {
  nextTick(() => {
    registCustom()
    initX6Node()
    window.addEventListener('resize', resizeGraph)
  })
})

onUnmounted(() => {
  if (graph.value) {
    graph.value.dispose()
    graph.value = null
  }
  window.removeEventListener('resize', resizeGraph)
})
</script>

<style scoped lang="scss">
.wrapper {
  width: 100%;
  height: 800px;
}
.title {
  width: 100%;
  text-align: center;
  font-size: 20px;
  font-weight: bold;
  padding: 10px 0;
}
.search {
  width: 100%;
  padding: 10px;
  display: flex;
  align-items: center;
}
#container {
  width: 100%;
  height: 600px;
  overflow: auto;
}
</style>
